package consumer

import (
	"context"
	"encoding/json"
	amqp "github.com/rabbitmq/amqp091-go"
	"github.com/sirupsen/logrus"
	"github.com/ztx/payment_project/common/broker"
	"github.com/ztx/payment_project/common/genproto/orderpd"
	"github.com/ztx/payment_project/payment/app"
	"github.com/ztx/payment_project/payment/app/command"
)

type Consumer struct {
	app app.Application
}

func NewConsumer(app app.Application) *Consumer {
	return &Consumer{
		app: app,
	}
}

// mq监听，消费消息
func (c *Consumer) Listen(ch *amqp.Channel) {
	q, err := ch.QueueDeclare(broker.EventOrderCreated, true, false, false, false, nil)
	if err != nil {
		logrus.Fatal(err)
	}

	//读取队列消息
	msgs, err := ch.Consume(q.Name, "", false, false, false, false, nil)
	if err != nil {
		logrus.Warnf("fail to consume: queue=%s, err=%v", q.Name, err)
	}

	var forever chan struct{}
	go func() {
		for msg := range msgs {
			c.handleMessage(msg)
		}
	}()
	<-forever
}

// 消费消息逻辑----创建支付链接
func (c *Consumer) handleMessage(msg amqp.Delivery) {

	o := &orderpd.Order{}
	if err := json.Unmarshal(msg.Body, o); err != nil { //转换类型失败
		logrus.Infof("failed to unmarshall msg to order, err = %v", err)
		_ = msg.Nack(false, false)
		return
	}

	if _, err := c.app.Commands.CreatePayment.Handle(context.TODO(), command.CreatePayment{Order: o}); err != nil {
		//TODO  retry
		logrus.Infof("failed to create order , err= %v", err)
		_ = msg.Nack(false, false)
		return
	}

	_ = msg.Ack(false) //回应ack
}
